using System;
using Oracle.ManagedDataAccess.Client;
using OracleInternal.BulkCopy;
using OracleInternal.Common;
using OracleInternal.Network;
using OracleInternal.ServiceObjects;

namespace OracleInternal.TTC
{
	internal class TTCDirectPathLoadStream : TTCFunction
	{
		private const short ODPLS = 129;

		private const int DPLSDEF_IN_PARMCOUNT = 1;

		private const int DPLSDEF_IN_FLAG = 0;

		private const int DPLSDEF_IN_KLA_PARSE_RESET = 2;

		private const int STREAM_VERSION = 400;

		internal int m_DPLSVersion = 400;

		private long[] m_dplsi4;

		private int m_dplsi4l;

		private long[] m_dplso4;

		internal DirectPathContext m_directPathCtx;

		private long m_streamSize;

		private bool m_bInitHeader;

		private byte[] m_headerObBuffer;

		private int m_headerObPos;

		internal TTCDirectPathLoadStream(MarshallingEngine mEngine)
			: base(mEngine, 129, 0)
		{
			m_dplsi4 = new long[1];
			m_dplsi4l = 0;
			m_dplso4 = null;
		}

		internal void Init(DirectPathContext DPCtx)
		{
			m_directPathCtx = DPCtx;
		}

		internal void LoadStream(DirectPathStream dpStream)
		{
			if (dpStream.m_streamSize > 0)
			{
				MarshalHeader(dpStream.m_streamSize);
				MarshalStream(dpStream);
				ReadResponse();
				dpStream.Reset();
			}
		}

		private void MarshalStream(DirectPathStream dpStream)
		{
			DirectPathRow directPathRow = null;
			BulkCopyBindingRow bulkCopyBindingRow = null;
			DirectPathRowPiece directPathRowPiece = null;
			for (int i = 0; i < dpStream.m_dpRows.Count; i++)
			{
				directPathRow = dpStream.m_dpRows[i];
				bulkCopyBindingRow = dpStream.m_bindingRows[i];
				for (int j = 0; j < directPathRow.m_rowPieces.Count; j++)
				{
					directPathRowPiece = directPathRow.m_rowPieces[j];
					TTCDirectPathStreamMarshaller.MarshallRowPiece(m_marshallingEngine, bulkCopyBindingRow, directPathRowPiece);
				}
			}
		}

		internal void MarshalHeader(long streamSize)
		{
			WriteFunctionHeader();
			m_marshallingEngine.MarshalSWORD((int)m_directPathCtx.m_tableCursor);
			if (streamSize > 0)
			{
				m_marshallingEngine.MarshalPointer();
				m_headerObBuffer = m_marshallingEngine.m_oraBufWriter.m_currentObBuffer;
				m_headerObPos = m_marshallingEngine.m_oraBufWriter.m_positionInCurrentOB;
				m_marshallingEngine.MarshalUB4(streamSize);
			}
			else
			{
				m_marshallingEngine.MarshalNullPointer();
				m_marshallingEngine.MarshalUB4(0L);
			}
			m_marshallingEngine.MarshalUB4(m_DPLSVersion);
			if (m_dplsi4l > 0)
			{
				m_marshallingEngine.MarshalPointer();
			}
			else
			{
				m_marshallingEngine.MarshalNullPointer();
			}
			m_marshallingEngine.MarshalUB4(m_dplsi4l);
			m_marshallingEngine.MarshalPointer();
			m_marshallingEngine.MarshalPointer();
			m_bInitHeader = true;
		}

		internal void ReadResponse()
		{
			if (ProviderConfig.m_bTraceLevelPrivate)
			{
				Trace.Write(OracleTraceLevel.Private, (OracleTraceTag)131328, OracleTraceClassName.TTCTransactionEN, OracleTraceFuncName.ReadResponse);
			}
			bool flag = false;
			byte b = 0;
			try
			{
				m_marshallingEngine.TTCErrorObject.Initialize();
				while (!flag)
				{
					try
					{
						switch (m_marshallingEngine.UnmarshalSB1())
						{
						case 23:
							ProcessServerSidePiggybackFunction(0);
							break;
						case 8:
							Process_RPA_Message();
							break;
						case 15:
							m_marshallingEngine.TTCErrorObject.ReadWarning();
							break;
						case 4:
							flag = true;
							m_marshallingEngine.TTCErrorObject.ReadErrorMessage();
							if (m_marshallingEngine.TTCErrorObject.ErrorCode == 1403)
							{
								m_marshallingEngine.TTCErrorObject.Initialize();
							}
							else
							{
								OracleConnectionImpl.CheckForAnyErrorFromDB(m_marshallingEngine.TTCErrorObject);
							}
							break;
						case 9:
							if (m_marshallingEngine.HasEOCSCapability)
							{
								m_marshallingEngine.m_endOfCallStatus = m_marshallingEngine.UnmarshalUB4();
							}
							flag = true;
							break;
						default:
							throw new Exception("TTC error");
						}
					}
					catch (NetworkException ex)
					{
						if (ex.ErrorCode != 3111)
						{
							throw;
						}
						m_marshallingEngine.m_oracleCommunication.Reset();
					}
					catch (Exception)
					{
						if (m_marshallingEngine.m_oraBufRdr != null)
						{
							m_marshallingEngine.m_oraBufRdr.ClearState();
						}
						if (!flag)
						{
							m_marshallingEngine.m_oracleCommunication.Break();
							m_marshallingEngine.m_oracleCommunication.Reset();
							continue;
						}
						throw;
					}
				}
			}
			catch (Exception ex3)
			{
				OracleException.HandleError(OracleTraceLevel.Private, (OracleTraceTag)268566528, OracleTraceClassName.TTCTransactionEN, OracleTraceFuncName.ReadResponse, ex3);
				throw;
			}
			finally
			{
				if (ProviderConfig.m_bTraceLevelPrivate)
				{
					Trace.Write(OracleTraceLevel.Private, (OracleTraceTag)131584, OracleTraceClassName.TTCTransactionEN, OracleTraceFuncName.ReadResponse);
				}
			}
		}

		private void Process_RPA_Message()
		{
			int num = m_marshallingEngine.UnmarshalUB2();
			m_dplso4 = new long[num];
			for (int i = 0; i < num; i++)
			{
				m_dplso4[i] = m_marshallingEngine.UnmarshalUB4();
			}
		}
	}
}
